#include "renderer.h"
void renderer::Initialize(string windowCaption, string iconPath)
{
	if ( SDL_Init(SDL_INIT_AUDIO|SDL_INIT_VIDEO) < 0 )
	{ 
		MessageBox(NULL,  strcat("Unable to init SDL: ", SDL_GetError()), "SDL error", NULL); 
		exit(1); 
	}
	SDL_WM_SetCaption(windowCaption.c_str(),"");
	SDL_WM_SetIcon(SDL_LoadBMP(iconPath.c_str()), NULL);
	screen=SDL_SetVideoMode(640,480,32, SDL_HWSURFACE|SDL_DOUBLEBUF);
	//screen=SDL_SetVideoMode(640,480,32, SDL_HWSURFACE|SDL_DOUBLEBUF|SDL_FULLSCREEN);
	gameCamera.xCamera=0;
	gameCamera.yCamera=0;
	shouldDrawGrasp=false;
	selection=new gameobject(0,0,"tiles\\selection.bmp", 0xffffff, true, 16, 8, 0, 0, false, false, 0);
}
void renderer::RenderFrame(list<gameobject>* gameObjects, map* currentMap)
{

	SDL_FillRect(screen,NULL, 0x000000);
	
	std::list<mapElement>::iterator iterator1;
	for (iterator1 = currentMap->mapElements->begin(); iterator1 != currentMap->mapElements->end(); iterator1++) 
	{
		DrawDecoration(*iterator1);
	}
	if(shouldDrawGrasp)
	{
	DrawSelectionRect(screen, grasp.x, grasp.y, grasp.x+grasp.w, grasp.y+grasp.h, SDL_MapRGB(screen->format, 69, 205,50));
	}
	std::list<gameobject>::iterator iterator2;
	for (iterator2 = gameObjects->begin(); iterator2 != gameObjects->end(); iterator2++) 
	{
		DrawObject(*iterator2);
	}
	SDL_Flip(screen);
}
void renderer::DrawObject(gameobject& gObject)
{
	if(gObject.IsVisible() && renderer::InCamera(gObject.x,gObject.y))
	{
		if(gObject.controlled)
		{
			selection->x=gObject.x;
			selection->y=gObject.y;
			DrawObject(*selection);
		}
		SDL_Rect src,dest;
		src.x=0;
		src.y=0;
		src.w=(gObject.GetSurface())->w;
		src.h=(gObject.GetSurface())->h;
		dest.x=renderer::XMapToScr(gObject.x)-gObject.GetXMatch();
		dest.y=renderer::YMapToScr(gObject.y)-gObject.GetYMatch();
		dest.w=src.w;
		dest.h=src.h;
		SDL_BlitSurface(gObject.GetSurface(), &src, screen, &dest);
	}
}
bool renderer::InCamera(int x, int y)
{
	int xCam=gameCamera.xCamera
		, yCam=gameCamera.yCamera, wCam=screenWidthCells
		, hCam=screenHeightCells;
	return (x>=xCam-tileSize)&&(x<=xCam+wCam+tileSize)&&(y>=yCam-tileSize)&&(y<=yCam+wCam+tileSize);
}
int renderer::XMapToScr(int x)
{
	return (x-gameCamera.xCamera)*cellSize;
}
int renderer::YMapToScr(int y)
{
	return (y-gameCamera.yCamera)*cellSize;
}
int renderer::XScrToMap(int x)
{
	return x/cellSize+gameCamera.xCamera;
}
int renderer::YScrToMap(int y)
{
	return y/cellSize+gameCamera.yCamera;
}
void renderer::DrawRectangle(int x, int y, int w, int h, int color)
{
	grasp.x=x;
	grasp.y=y;
	grasp.h=h;
	grasp.w=w;
	graspColor=color;
}
void renderer::DrawDecoration(mapElement& decoration)
{
	if(decoration.link->IsVisible() && renderer::InCamera(decoration.x,decoration.y))
	{
		SDL_Rect src,dest;
		src.x=0;
		src.y=0;
		src.w=(decoration.link->GetSurface())->w;
		src.h=(decoration.link->GetSurface())->h;
		dest.x=renderer::XMapToScr(decoration.x)-decoration.link->GetXMatch();
		dest.y=renderer::YMapToScr(decoration.y)-decoration.link->GetYMatch();
		dest.w=src.w;
		dest.h=src.h;
		SDL_BlitSurface(decoration.link->GetSurface(), &src, screen, &dest);
	}
}
void renderer::DrawSelectionRect(SDL_Surface *screen, int x1, int y1, int x2, int y2, unsigned int color)
{
	for(int i=MIN(x1,x2);i<MAX(x1,x2);i++)
	{
		SetPixel( i, y1, color);
		SetPixel( i, y2, color);
	}
	for(int i=MIN(y1,y2);i<MAX(y1,y2);i++)
	{
		SetPixel( x1, i, color);
		SetPixel( x2, i, color);
	}
}
void renderer::SetPixel(int x, int y, Uint32 color)
{
	Uint32 bpp, ofs;

	bpp = screen->format->BytesPerPixel;
	ofs = screen->pitch*y + x*bpp;

	SDL_LockSurface(screen);
	memcpy((void *) ((Uint32)(screen->pixels) + ofs), &color, bpp);
	SDL_UnlockSurface(screen);
}